package auctionhaus



import org.junit.*
import grails.test.mixin.*
import grails.converters.JSON
import org.json.simple.JSONObject

@TestFor(ListingController)
@Mock([Listing, Customer, Bid])
class ListingControllerUnitTests {

    @Test
    void testPlaceBid() {
        def alice = new Customer(emailAddress: 'alice@umn.edu', password: 'password').save(flush: true, failOnError: true)
        session.customer = alice
        alice.bids = new HashSet<Bid>()
        alice.listings = new HashSet<Listing>()
        alice.save(flush: true, failOnError: true)

        def listing = new Listing(name: 'volleyball', endDateTime: new Date() + 5, seller: alice, startingBidAmount: 20).save(failOnError: true)
        listing.bids = new HashSet<Bid>()
        listing.save(flush: true, failOnError: true)

        params.id = listing.id
        params.amount = '20.50'
        controller.listingService = new ListingService()
        controller.placeBid();

        def json = controller.response.contentAsString
        def jsonMap = JSON.parse(json);

        assert response.contentType.contains("application/json")
        assert !jsonMap.error
        assert jsonMap.message == "Bid successfully placed."
        assert jsonMap.amount == 20.50
        assert jsonMap.listingId == listing.id

    }

    void testPlaceInvalidBid() {
        def alice = new Customer(emailAddress: 'alice@umn.edu', password: 'password').save(flush: true, failOnError: true)
        session.customer = alice
        alice.bids = new HashSet<Bid>()
        alice.listings = new HashSet<Listing>()
        alice.save(flush: true, failOnError: true)

        def listing = new Listing(name: 'volleyball', endDateTime: new Date() + 5, seller: alice, startingBidAmount: 20).save(failOnError: true)
        listing.bids = new HashSet<Bid>()
        listing.save(flush: true, failOnError: true)

        params.id = listing.id
        params.amount = 'invalid bid'
        controller.listingService = new ListingService()
        controller.placeBid();

        def json = controller.response.contentAsString
        def jsonMap = JSON.parse(json);

        assert response.contentType.contains("application/json")
        assert jsonMap.error
        assert jsonMap.message == "Must enter a valid price."
        assert jsonMap.listingId == listing.id

    }

    void testBidTooSmall() {
        def alice = new Customer(emailAddress: 'alice@umn.edu', password: 'password').save(flush: true, failOnError: true)
        session.customer = alice
        alice.bids = new HashSet<Bid>()
        alice.listings = new HashSet<Listing>()
        def listing = new Listing(name: 'bicycle', endDateTime: new Date() + 5, seller: alice, startingBidAmount: 100, description: 'desc')
        def bid = new Bid(bidder: alice, listing: listing , amount: 105)
        listing.addToBids(bid)
        listing.save(flush: true, failOnError: true)
        alice.bids.add(bid)
        alice.save(flush: true, failOnError: true)
        params.id = listing.id
        params.amount = '105.25'
        controller.listingService = new ListingService()
        controller.placeBid();

        def json = controller.response.contentAsString
        def jsonMap = JSON.parse(json);

        assert response.contentType.contains("application/json")
        assert jsonMap.error
        assert jsonMap.message == "Bid must be at least 50 cents greater than current bid."
        assert jsonMap.listingId == listing.id
    }

    void testFirstBidTooSmall() {
        def alice = new Customer(emailAddress: 'alice@umn.edu', password: 'password').save(flush: true, failOnError: true)
        session.customer = alice
        alice.bids = new HashSet<Bid>()
        alice.listings = new HashSet<Listing>()
        alice.save(flush: true, failOnError: true)

        def listing = new Listing(name: 'volleyball', endDateTime: new Date() + 5, seller: alice, startingBidAmount: 20).save(failOnError: true)
        listing.bids = new HashSet<Bid>()
        listing.save(flush: true, failOnError: true)

        params.id = listing.id
        params.amount = '10'
        controller.listingService = new ListingService()
        controller.placeBid();

        def json = controller.response.contentAsString
        def jsonMap = JSON.parse(json);

        assert response.contentType.contains("application/json")
        assert jsonMap.error
        assert jsonMap.message == "Bid must be at least 50 cents greater than starting bid."
        assert jsonMap.listingId == listing.id
    }

}

